package com.cqc.jdk8.Jutil;

import com.cqc.eb.PersonEB;
import org.junit.Test;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.function.BiFunction;

public class MapTest {

    /**
     * putAll(map)
     */
    @Test
    public void putAll() {
        Map<String, List<PersonEB>> map1 = new HashMap<>();
        List<PersonEB> list1 = new ArrayList<>();
        list1.add(new PersonEB(1, "张三"));
        map1.put("1", list1);

        Map<String, List<PersonEB>> resultMap = new HashMap<>();
        List<PersonEB> list2 = new ArrayList<>();
        list2.add(new PersonEB(1, "李四"));
        resultMap.put("1", list2);

        resultMap.putAll(map1);

        System.out.println(1);
    }

    /**
     * 不需要重新赋值
     */
    @Test
    public void f2() {
        Map<String, List<PersonEB>> map1 = new HashMap<>();
        List<PersonEB> list1 = new ArrayList<>();
        list1.add(new PersonEB(1, "张三"));
        map1.put("1", list1);

        List<PersonEB> personEBList = map1.get("1");
        personEBList.add(new PersonEB(2, "李四"));

        System.out.println(1);
    }

    @Test
    public void f3() {
        Map<String, String> map = new HashMap<>();
        map.put("1", "张三");
        map.put("2", "李一");//null
        //value为null，才会put
        String value1 = map.putIfAbsent("2", "李四");
        System.out.println("putIfAbsent=" + value1);
        //如果获取不到value，则给默认值
        String value2 = map.getOrDefault("2", "李四2");
        System.out.println(value2);

        //foreach遍历
        map.forEach((key, value) -> {
            System.out.println(key + "=" + value);
        });
    }

    @Test
    public void replace() {
        Map<String, String> map = new HashMap<>();
        map.put("1", "张三");
        map.put("2", "李四");
        map.put("3", "王五");
        //替换value
        map.replace("3", "王五2");

        //newValue = oldValue+"A"
        //map.replaceAll((k, v) -> v + "A");

        //foreach遍历
        map.forEach((key, value) -> {
            System.out.println(key + "=" + value);
        });
    }

    /**
     *
     */
    @Test
    public void merge() {
        Map<String, String> map = new HashMap<>();
        map.put("1", "张三");
        //map.merge("1", "李四", new BiFunction<String, String, String>() {
        //    @Override
        //    public String apply(String oldValue, String newValue) {
        ////oldValue表示key=1对应的值，newValue是第2个参数value,是新值
        //        return oldValue + newValue;
        //    }
        //});

        //lambada写法
//        map.merge("1", "李四", (oldValue, value) -> oldValue + value);
        map.merge("2", "李四", (oldValue, value) -> oldValue + value);
        System.out.println(map);
    }

    @Test
    public void merge2() {
        List<String> list = new ArrayList<>();
        list.add("A");
        list.add("B");
        list.add("A");
        list.add("C");
        list.add("A");

        //统计每个字母出现的次数
        Map<String, Integer> map = new HashMap<>();
        for (String item : list) {
            //map.merge(item, 1, new BiFunction<Integer, Integer, Integer>() {
            //    @Override
            //    public Integer apply(Integer oldValue, Integer value) {
            //        //value就是merge的第2个参数value
            //        return oldValue + value;
            //    }
            //});
            //简单写法
            map.merge(item, 1, Integer::sum);
//            map.merge(item, 1, (x,y)->x+y);
        }

        map.forEach((key, value) -> {
            System.out.println(key + "=" + value);
        });
    }

    /**
     * merge(key,value,BiFunction)
     */
    @Test
    public void compute() {
        List<String> list = new ArrayList<>();
        list.add("A");
        list.add("B");
        list.add("A");
        list.add("C");
        list.add("A");

        //统计每个字母出现的次数
        Map<String, Integer> map = new HashMap<>();
        for (String item : list) {
//            Integer compute = map.compute(item, new BiFunction<String, Integer, Integer>() {
//
//                @Override
//                public Integer apply(String k, Integer v) {
//                    if (v == null) {
//                        v = 1;
//                    } else {
//                        v += 1;
//                    }
//                    //如果返回null，那么map会remove(key)
//                    if (k.equals("C")) {
//                        return null;
//                    }
//                    return v;
//                }
//            });
            //返回value的最新值. k就是item
            Integer compute = map.compute(item, (k, v) -> {
                if (v == null) {
                    v = 1;
                } else {
                    v += 1;
                }
                //如果返回null，那么map会remove(key)
                if (k.equals("C")) {
                    return null;
                }
                return v;
            });
            //System.out.println(item + "=" + compute);
        }

        map.forEach((key, value) -> {
            System.out.println(key + "=" + value);
        });
    }

    /**
     * 如果key对应的值存在，才会执行BiFunction，并返回BiFunction的结果。如果BiFunction的结果是null，则移除key
     * 如果key对应的值不存在，不会执行BiFunction，并返回null。
     */
    @Test
    public void computeIfPresent() {
        Map<String, String> map = new HashMap<>();
        map.put("1", "张三");
        String value = map.computeIfPresent("2", (k, v) -> v + "2");
        //String value = map.computeIfPresent("1", (k, v) -> null);
        System.out.println(value);
        System.out.println(map);
    }

    /**
     * 如果key对应的值不存在，才会执行BiFunction，如果BiFunction的结果不为null，则赋给value，并返回value
     * 如果key对应的值存在，则不执行BiFunction，并返回value
     */
    @Test
    public void computeIfAbsent() {
        Map<String, String> map = new HashMap<>();
        map.put("1", "张三");
        map.put("2", "李四");
        String value = map.computeIfAbsent("3", k -> "王五");
        System.out.println(value);
        System.out.println(map);
    }
}
